using System;
using System.Collections.Generic;
using System.Text;

using Microsoft.SharePoint.WebControls;
using System.Web.UI.WebControls;
using System.Globalization;

namespace ASPNETLibrary.SharePoint.WebControls
{
    /// <summary>
    /// Represents a grid view that looks and behaves like a tree view. It inherits from 
    /// SPGridView and overrides a few properties of base class to allow custom paging.
    /// It should be very usefull in cases where very large result sets should be displayed
    /// but not all of the results should be retrieved from data store at once.
    /// </summary>
    public class SPPagedGridView : SPGridView
    {
        #region Private constants
        private const string ItemCountViewStateKey = "sppgv_virtitemcount";
        private const string PageIndexViewStateKey = "sppgv_currentpageindex";
        private const int ItemCountNoItems = -1;
        #endregion Private constants

        #region Overrides
        protected override void InitializePager(System.Web.UI.WebControls.GridViewRow row, int columnSpan, System.Web.UI.WebControls.PagedDataSource pagedDataSource)
        {
            //We override InitializePager to set a few properties before InitializePager is called
            //from base class. This way we will implement custom paging but will still use the
            //default pager control.
            if (this.CustomPagingTurnedOn)
            {
                pagedDataSource.AllowCustomPaging = true;
                pagedDataSource.VirtualCount = this.VirtualItemCount;
                pagedDataSource.CurrentPageIndex = this.CurrentPageIndex;
            }
            base.InitializePager(row, columnSpan, pagedDataSource);
        }
        #endregion Overrides

        #region Public properties
        /// <summary>
        /// Gets or sets the total number of items in result set no matter
        /// how many items will be shown per page.
        /// For example, if total number of items that should be shown by 
        /// the grid is 2356002 but only 10 items should be shown per page then
        /// this property will be set to 2356002.
        /// </summary>
        public int VirtualItemCount
        {
            get
            {
                int retVal = SPPagedGridView.ItemCountNoItems;

                if (ViewState[SPPagedGridView.ItemCountViewStateKey] == null)
                {
                    ViewState[SPPagedGridView.ItemCountViewStateKey] = SPPagedGridView.ItemCountNoItems;
                }
                else
                {
                    retVal = Convert.ToInt32(ViewState[SPPagedGridView.ItemCountViewStateKey], CultureInfo.InvariantCulture);
                }
                return retVal;
            }
            set
            {
                ViewState[SPPagedGridView.ItemCountViewStateKey] = value;
            }
        }

        /// <summary>
        /// Gets or sets the object from which the data-bound control retrieves its list of
        /// data items. This property should be set to a list of items that should be shown
        /// on a particular/current page.
        /// </summary>
        public override object DataSource
        {
            get
            {
                return base.DataSource;
            }
            set
            {
                base.DataSource = value;
                // we store the page index here so we dont lost it in databind
                this.CurrentPageIndex = this.PageIndex;
            }
        }
        #endregion Public properties

        #region Private properties
        private bool CustomPagingTurnedOn
        {
            get
            {
                //If VirtualItemCount is set (any value different than -1) then
                //we say custom paging is turned on.
                return (this.VirtualItemCount != SPPagedGridView.ItemCountNoItems);
            }
        }

        private int CurrentPageIndex
        {
            get
            {
                int retVal = 0;
                if (ViewState[SPPagedGridView.PageIndexViewStateKey] == null)
                {
                    ViewState[SPPagedGridView.PageIndexViewStateKey] = 0;
                }
                else
                {
                    retVal = Convert.ToInt32(ViewState[SPPagedGridView.PageIndexViewStateKey], CultureInfo.InvariantCulture);
                }
                return retVal;
            }
            set
            {
                ViewState[SPPagedGridView.PageIndexViewStateKey] = value;
            }
        }

        #endregion Private properties
    }
}
